//
//  CallViewController.m
//  VidoarDemo
//
//  Created by xm on 2025/7/23.
//

#import "CallViewController.h"
#import <CallKit/CallKit.h>
#import <UserNotifications/UserNotifications.h>
#import <Contacts/Contacts.h>



@interface CallViewController ()<CXCallObserverDelegate, UNUserNotificationCenterDelegate>
@property(nonatomic, strong) UIButton *startButton;
@property(nonatomic, assign) BOOL groupStatus;
@property(nonatomic, assign) BOOL callExtensionStatus;

@property (nonatomic, strong) CXCallObserver *callObserver;

@end

@implementation CallViewController

static NSString* CallExtensionBundleID = @"com.vidoar.demo.DemoCall";
static NSString* AppGroupBundleID = @"group.com.vidoar.demo";

#pragma mark - init

- (void)viewDidLoad
{
    [super viewDidLoad];
    // Do any additional setup after loading the view.
    [self setup];
    
}

-(void) setup
{
    [self createdUI];
    [self watch];
    [self checkAppGroup];
    [self.callObserver setDelegate:self queue:nil];
    [self notificationTest];
}

-(void) createdUI
{
    [self.view addSubview:self.startButton];

}

-(void) watch
{
    [[self.startButton rac_signalForControlEvents:UIControlEventTouchDown] subscribeNext:^(__kindof UIControl * _Nullable x) {
        
        [self startAction];
        
    }];
    
    [RACObserve(self, groupStatus) subscribeNext:^(id  _Nullable x) {
        
        if(self.groupStatus){
            
//            [self reloadExtension];
            [self checkExtensionStatus];

        }
    }];
    
    [RACObserve(self, callExtensionStatus) subscribeNext:^(id  _Nullable x) {
        
        if(self.callExtensionStatus){
            
        }
    }];
    

    
}

#pragma mark contacts
- (void)fetchContacts {
    CNAuthorizationStatus status = [CNContactStore authorizationStatusForEntityType:CNEntityTypeContacts];
    
    if (status == CNAuthorizationStatusDenied || status == CNAuthorizationStatusRestricted) {
        [self showPermissionAlert];
        return;
    }
    
    CNContactStore *store = [[CNContactStore alloc] init];
    [store requestAccessForEntityType:CNEntityTypeContacts completionHandler:^(BOOL granted, NSError * _Nullable error) {
        if (granted) {
            [self retrieveContactsFromStore:store];
        } else {
            NSLog(@"Access to contacts denied");
        }
    }];
}

- (void)retrieveContactsFromStore:(CNContactStore *)store {
    NSArray *keysToFetch = @[
        CNContactGivenNameKey,
        CNContactFamilyNameKey,
        CNContactPhoneNumbersKey,
        CNContactEmailAddressesKey,
        CNContactPostalAddressesKey,
        CNContactOrganizationNameKey,
        CNContactJobTitleKey,
        CNContactImageDataKey
    ];
    
    CNContactFetchRequest *fetchRequest = [[CNContactFetchRequest alloc] initWithKeysToFetch:keysToFetch];
    NSMutableArray *contacts = [NSMutableArray array];
    
    NSError *error;
    [store enumerateContactsWithFetchRequest:fetchRequest error:&error usingBlock:^(CNContact * _Nonnull contact, BOOL * _Nonnull stop) {
        [contacts addObject:contact];
    }];
    
    if (error) {
        NSLog(@"Error fetching contacts: %@", error);
    } else {
        dispatch_async(dispatch_get_main_queue(), ^{
            [self processContacts:contacts];
        });
    }
}

- (void)processContacts:(NSArray<CNContact *> *)contacts {
    for (CNContact *contact in contacts) {
        NSString *fullName = [NSString stringWithFormat:@"%@ %@", contact.givenName, contact.familyName];
        NSLog(@"Contact: %@", fullName);
        
        for (CNLabeledValue *phoneNumber in contact.phoneNumbers) {
            NSString *label = [CNLabeledValue localizedStringForLabel:phoneNumber.label];
            CNPhoneNumber *number = phoneNumber.value;
            NSLog(@"Phone: %@ - %@", label, number.stringValue);
        }
        
        for (CNLabeledValue *email in contact.emailAddresses) {
            NSString *label = [CNLabeledValue localizedStringForLabel:email.label];
            NSString *emailAddress = email.value;
            NSLog(@"Email: %@ - %@", label, emailAddress);
        }
    }
}

- (void)showPermissionAlert {
    UIAlertController *alert = [UIAlertController alertControllerWithTitle:@"权限被拒绝"
                                                                   message:@"请在设置中允许访问通讯录"
                                                            preferredStyle:UIAlertControllerStyleAlert];
    
    [alert addAction:[UIAlertAction actionWithTitle:@"去设置" style:UIAlertActionStyleDefault handler:^(UIAlertAction * _Nonnull action) {
        [[UIApplication sharedApplication] openURL:[NSURL URLWithString:UIApplicationOpenSettingsURLString] options:@{} completionHandler:nil];
    }]];
    
    [alert addAction:[UIAlertAction actionWithTitle:@"取消" style:UIAlertActionStyleCancel handler:nil]];
    
    [self presentViewController:alert animated:YES completion:nil];
}

#pragma  mark notification


-(void) notificationTest
{
    // 请求通知权限
    UNUserNotificationCenter *center = [UNUserNotificationCenter currentNotificationCenter];
    [center requestAuthorizationWithOptions:(UNAuthorizationOptionAlert | UNAuthorizationOptionSound)
                        completionHandler:^(BOOL granted, NSError * _Nullable error) {
        if (granted) {
            NSLog(@"通知权限已授权");
        }
    }];
}

// 实现UNUserNotificationCenterDelegate方法
- (void)userNotificationCenter:(UNUserNotificationCenter *)center
       willPresentNotification:(UNNotification *)notification
         withCompletionHandler:(void (^)(UNNotificationPresentationOptions))completionHandler {
    
    self.log(@"xxx %@", notification.request.content.title);
    // 检查是否是微信通知
    if ([notification.request.content.title containsString:@"微信"] ||
        [notification.request.identifier hasPrefix:@"com.tencent.xin"]) {
        NSLog(@"检测到微信通知");
        // 这里只能获取通知的标题、子标题等基本信息，无法获取具体消息内容
    }
    
    completionHandler(UNNotificationPresentationOptionNone);
}

#pragma  makr - getters

- (UIButton *)startButton
{
    if(_startButton){
        return _startButton;
    }
    
    CGRect frame = CGRectMake(20, NavAndStatusToolHeight + 20, screenWidth-40, 46);
    UIButton* button = [self createButtonWithTitle:@"开始" frame:frame];
    
    _startButton = button;
    return _startButton;
    
}

- (CXCallObserver *)callObserver
{
    if(_callObserver == nil){
        _callObserver = [[CXCallObserver alloc] init];
    }
    
    return _callObserver;;
}

#pragma mark - method


- (void)showEnableExtensionAlert {
    dispatch_async(dispatch_get_main_queue(), ^{
        UIAlertController *alert = [UIAlertController alertControllerWithTitle:@"启用来电识别"
                                                                       message:@"请在设置中启用来电识别功能"
                                                                preferredStyle:UIAlertControllerStyleAlert];
        
        [alert addAction:[UIAlertAction actionWithTitle:@"去设置" style:UIAlertActionStyleDefault handler:^(UIAlertAction * _Nonnull action) {
            [[UIApplication sharedApplication] openURL:[NSURL URLWithString:UIApplicationOpenSettingsURLString] options:@{} completionHandler:nil];
        }]];
        
        [alert addAction:[UIAlertAction actionWithTitle:@"取消" style:UIAlertActionStyleCancel handler:nil]];
        
        [self presentViewController:alert animated:YES completion:nil];
    });
    
    

}

- (void)reloadExtension
{
    self.log(@"reloadExtension");

    CXCallDirectoryManager *manager = [CXCallDirectoryManager sharedInstance];
    [manager reloadExtensionWithIdentifier:CallExtensionBundleID completionHandler:^(NSError * _Nullable error) {
        if (error) {
            NSLog(@"重新加载扩展失败: %@", error);
        } else {
            NSLog(@"重新加载扩展成功");
        }
    }];
}

- (void)checkExtensionStatus
{
    self.log(@"checkExtensionStatus");
    CXCallDirectoryManager *manager = [CXCallDirectoryManager sharedInstance];
    [manager getEnabledStatusForExtensionWithIdentifier:CallExtensionBundleID completionHandler:^(CXCallDirectoryEnabledStatus enabledStatus, NSError * _Nullable error) {
        if (error) {
            NSLog(@"检查扩展状态错误: %@", error);
            return;
        }
        
        switch (enabledStatus) {
            case CXCallDirectoryEnabledStatusUnknown:
                NSLog(@"状态未知");
                break;
            case CXCallDirectoryEnabledStatusDisabled:
                NSLog(@"用户已禁用");
                
                [self showEnableExtensionAlert];

                break;
            case CXCallDirectoryEnabledStatusEnabled:
                NSLog(@"已启用");
                self.callExtensionStatus = YES;
                break;
        }
    }];
}

- (void)identifyIncomingCall
{
    self.log(@"identifyIncomingCall");
    // 获取共享容器中的电话号码数据
    NSURL *sharedContainerURL = [[NSFileManager defaultManager] containerURLForSecurityApplicationGroupIdentifier:AppGroupBundleID];
    self.log(@"sharedContainerURL: %@", sharedContainerURL.path);
    [self listFilesRecursivelyInDirectory:sharedContainerURL.path];
    NSURL *dataFileURL = [sharedContainerURL URLByAppendingPathComponent:@"CallDirectoryData"];
    
    if ([[NSFileManager defaultManager] fileExistsAtPath:dataFileURL.path]) {
        NSDictionary *phoneNumbers = [NSDictionary dictionaryWithContentsOfURL:dataFileURL];
        self.log(@"XXX phoneNumbers: ", [phoneNumbers mj_JSONString]);
        
        // 在实际应用中，这里需要获取当前来电号码
        // 由于iOS限制，无法直接获取来电号码，需要通过其他方式匹配
        // 例如通过CXCallDirectoryExtension预先标记的号码
        
        NSLog(@"Loaded %lu phone numbers from shared container", (unsigned long)phoneNumbers.count);
    }
}

-(void) checkAppGroup
{
    self.log(@"checkAppGroup");
    // 检查 App Group 是否可用
    NSFileManager *manager = [NSFileManager defaultManager];
    NSURL *containerURL = [manager containerURLForSecurityApplicationGroupIdentifier: AppGroupBundleID];
    if (!containerURL) {
        self.log(@"App Group 配置错误");
    }else{
        self.log(@"App Group 配置成功 %@", containerURL);
        [self listFilesRecursivelyInDirectory:containerURL.path];
        self.groupStatus = YES;
    }
}

// 存储号码识别数据
//- (void)savePhoneNumbersToSharedContainer {
//    NSDictionary* phoneNumbers = @{
//        @[@"18220850027", @"xumeng"],
//        @[@"18220850027", @"xumeng"],
//    };
//    NSUserDefaults *sharedDefaults = [[NSUserDefaults alloc] initWithSuiteName:AppGroupBundleID];
//    [sharedDefaults setObject:phoneNumbers forKey:@"callDirectoryData"];
//    [sharedDefaults synchronize];
//}

// 扩展中读取数据
- (NSDictionary<NSNumber *, NSString *> *)loadPhoneNumbersFromSharedContainer {
    NSUserDefaults *sharedDefaults = [[NSUserDefaults alloc] initWithSuiteName:AppGroupBundleID];
    return [sharedDefaults objectForKey:@"callDirectoryData"];
}


-(UIButton*) createButtonWithTitle:(NSString*)title frame:(CGRect) frame
{
    UIButton * button = [UIButton buttonWithType:UIButtonTypeCustom];
    [button setTitle:title forState:UIControlStateNormal];
    button.top = frame.origin.y;
    button.left = frame.origin.x;
    button.width = frame.size.width;
    button.height = frame.size.height;
    
    button.layer.cornerRadius = 5;
    button.layer.masksToBounds = YES;
    button.titleLabel.textAlignment = NSTextAlignmentCenter;
    [button setTitleColor:[UIColor colorWithHexString:@"FFFFFF"] forState:UIControlStateNormal];
    [button.titleLabel setFont:[UIFont systemFontOfSize:20]];
    [button setBackgroundColor:[UIColor colorWithHexString:@"5974A4"]];
    
    return button;
}

#pragma mark - CXCallObserverDelegate

- (void)callObserver:(CXCallObserver *)callObserver callChanged:(CXCall *)call {
    if (call.hasConnected) {
        // 电话已接通
        NSLog(@"Call connected");
    } else if (call.hasEnded) {
        // 电话已结束
        NSLog(@"Call ended");
    } else if (call.isOutgoing && !call.hasConnected) {
        // 正在拨出电话
        NSLog(@"Dialing out");
    } else if (!call.hasConnected && !call.hasEnded && !call.isOutgoing) {
        // 来电呼入
        NSLog(@"Incoming call %@", call.UUID.UUIDString);
        [self identifyIncomingCall];
    } else {
        // 其他状态
        NSLog(@"Call state changed");
    }
}

#pragma  mark - actions

-(void) startAction
{
    self.log(@"startAction");
    [self fetchContacts];
}

#pragma mark - others
- (void)listFilesRecursivelyInDirectory:(NSString *)directoryPath {
    NSFileManager *fileManager = [NSFileManager defaultManager];
    NSDirectoryEnumerator *enumerator = [fileManager enumeratorAtPath:directoryPath];
    
    NSString *file;
    while ((file = [enumerator nextObject])) {
        // 跳过隐藏文件（可选）
        if ([file hasPrefix:@"."]) {
            continue;
        }
        
        BOOL isDirectory;
        NSString *fullPath = [directoryPath stringByAppendingPathComponent:file];
        [fileManager fileExistsAtPath:fullPath isDirectory:&isDirectory];
        
        if (isDirectory) {
            NSLog(@"Directory: %@", file);
        } else {
            NSLog(@"File: %@", file);
        }
    }
}

@end
